//
//  SourceListCell.m
//  SolarSeek
//
//  Created by Erick Fejta on 05/04/07.
//  Copyright 2005 Erick Fejta. All rights reserved.
//

#import "SourceListCell.h"
#import "SourceListElement.h"
#import "EnumTypes.h"
#import "Peers.h"

@interface NSObject (Peerable)
- (Peer *)peer;
@end

@implementation SourceListCell
- (id)init {
	if(self = [super init]) {
		_imageLeft =  [[NSImageCell alloc] init];
		[_imageLeft setImageAlignment:NSImageAlignCenter];
		[_imageLeft setImageScaling:NSScaleProportionally];
	}
	return self;
}

- (void)awakeFromNib {
	_imageLeft =  [[NSImageCell alloc] init];
	[_imageLeft setImageAlignment:NSImageAlignCenter];
	[_imageLeft setImageScaling:NSScaleProportionally];
}

- (id)copyWithZone:(NSZone *)zone {
	SourceListCell *slc = [super copyWithZone:zone];
	if(slc) {
		slc->_imageLeft = [[NSImageCell alloc] init];
		[slc->_imageLeft setImageScaling:NSScaleProportionally];
		[slc->_imageLeft setImageAlignment:NSImageAlignCenter];
		[slc->_imageLeft setImage:[_imageLeft image]];
	}
	return slc;
}

- (void)dealloc {
	[_imageLeft release];
	[super dealloc];
}

#pragma mark -

- (void)setObjectValue:(id)obj {
	if([obj conformsToProtocol:@protocol(SourceListElement)]) {
		SourceListElement *sle = obj;
		[super setAttributedStringValue:[sle nameAttributed]];
		[_imageLeft setObjectValue:[sle icon]];
	}
	else
		[super setObjectValue:obj];
}

#pragma mark -

- (void)drawInteriorWithFrame:(NSRect)frame inView:(NSView *)view {
	if([_imageLeft image]) {
		NSRect iconslice, textslice;
		NSDivideRect(frame,&iconslice,&textslice,22,NSMinXEdge);
		iconslice.size.width = 22;
		[_imageLeft drawInteriorWithFrame:iconslice inView:view];
		textslice.origin.y+=2;
		textslice.size.height-=2;
		[super drawInteriorWithFrame:textslice inView:view];
	}
	else {
		[super drawInteriorWithFrame:frame inView:view];
	}
}

@end

@implementation AvailabilityCell
- (id)setObjectValue:(id)object {
	if([object respondsToSelector:@selector(intValue)]) {
		available = [object intValue];
	}
	else if([object isKindOfClass:[Peer class]]) {
		available = [(Peer *)object availability];
	}
	else if([object respondsToSelector:@selector(peer)]) {
		available = [(Peer *)[object peer] availability];
	}
	else {
		available = AvailabilityUnknown;
	}
}

- (void)drawInteriorWithFrame:(NSRect)frame inView:(NSView *)view {
	NSRect iconslice=frame;
	float ideal = 8;
	float dY = iconslice.size.height>ideal?(iconslice.size.height-ideal)/2:0;
	float dX = iconslice.size.width>ideal?(iconslice.size.width-ideal)/2:0;
	iconslice = NSInsetRect(iconslice,dX,dY);
	
	NSBezierPath *bp = [NSBezierPath bezierPathWithRect:iconslice];
	NSColor *c=nil;
	switch(available) {
		case AvailabilityOnline: {
			bp = [NSBezierPath bezierPathWithOvalInRect:iconslice];
			c = [NSColor colorWithCalibratedRed:0.15 green:0.70 blue:0.0 alpha:1.0];
			if([self isHighlighted])
				[[c highlightWithLevel:0.5] set];
			else
				[c set];
			[bp fill];
			break;
		}
		case AvailabilityAway:
			[bp setLineJoinStyle:NSMiterLineJoinStyle];
			c = [NSColor colorWithCalibratedRed:0.8 green:0 blue:0 alpha:1.0];
			if([self isHighlighted])
				[[c highlightWithLevel:0.5] set];
			else
				[c set];
			[NSBezierPath fillRect:iconslice];
			break;
		case AvailabilityOffline:
			[bp setLineJoinStyle:NSMiterLineJoinStyle];
			c = [NSColor colorWithCalibratedRed:0.091 green:0.070 blue:0.008 alpha:1.0];
			if([self isHighlighted])
				[[c highlightWithLevel:0.5] set];
			else
				[c set];
			[NSBezierPath strokeRect:iconslice];
			break;
		default:
			[bp setLineJoinStyle:NSRoundLineJoinStyle];
			c = [NSColor colorWithCalibratedRed:0.341 green:0.310 blue:0.016 alpha:1.0];
			if([self isHighlighted])
				[[c highlightWithLevel:0.5] set];
			else
				[c set];
			iconslice = NSInsetRect(iconslice,0.0,iconslice.size.height/4.0);
			[NSBezierPath fillRect:iconslice];
	}
}
@end
#pragma mark -

@implementation UserListCell

- (id)setObjectValue:(id)object {
	if([object isKindOfClass:[Peer class]]) {
		available = [(Peer *)object availability];
		[super setObjectValue:[(Peer *)object name]];
	}
	else if([object respondsToSelector:@selector(peer)]) {
		available = [(Peer *)[object peer] availability];
		[super setObjectValue:object];
	}
	else {
		available = AvailabilityUnknown;
		[super setObjectValue:object];
	}
}

- (void)drawInteriorWithFrame:(NSRect)frame inView:(NSView *)view {
	NSRect iconslice, textslice;
	NSDivideRect(frame,&iconslice,&textslice,14,NSMinXEdge);
	float ideal = 8;
	float dY = iconslice.size.height>ideal?(iconslice.size.height-ideal)/2:0;
	float dX = iconslice.size.width>ideal?(iconslice.size.width-ideal)/2:0;
	iconslice = NSInsetRect(iconslice,dX,dY);
	
	[super drawInteriorWithFrame:textslice inView:view];
	NSBezierPath *bp = [NSBezierPath bezierPathWithRect:iconslice];
	NSColor *c=nil;
	switch(available) {
		case AvailabilityOnline: {
			bp = [NSBezierPath bezierPathWithOvalInRect:iconslice];
			c = [NSColor colorWithCalibratedRed:0.15 green:0.70 blue:0.0 alpha:1.0];
			if([self isHighlighted])
				[[c highlightWithLevel:0.5] set];
			else
				[c set];
			[bp fill];
			break;
		}
		case AvailabilityAway:
			[bp setLineJoinStyle:NSMiterLineJoinStyle];
			c = [NSColor colorWithCalibratedRed:0.8 green:0 blue:0 alpha:1.0];
			if([self isHighlighted])
				[[c highlightWithLevel:0.5] set];
			else
				[c set];
			[NSBezierPath fillRect:iconslice];
			break;
		case AvailabilityOffline:
			[bp setLineJoinStyle:NSMiterLineJoinStyle];
			c = [NSColor colorWithCalibratedRed:0.091 green:0.070 blue:0.008 alpha:1.0];
			if([self isHighlighted])
				[[c highlightWithLevel:0.5] set];
			else
				[c set];
			[NSBezierPath strokeRect:iconslice];
			break;
		default:
			[bp setLineJoinStyle:NSRoundLineJoinStyle];
			c = [NSColor colorWithCalibratedRed:0.341 green:0.310 blue:0.016 alpha:1.0];
			if([self isHighlighted])
				[[c highlightWithLevel:0.5] set];
			else
				[c set];
			iconslice = NSInsetRect(iconslice,0.0,iconslice.size.height/4.0);
			[NSBezierPath fillRect:iconslice];
	}
}

@end 